home *** CD-ROM | disk | FTP | other *** search
/ Aminet 1 / Aminet - June 1993 [Walnut Creek].iso / usenet / sources / volume90 / util / app_2_0 / part01
Encoding:
Internet Message Format  |  1990-07-02  |  39.5 KB

  1. Path: xanth!cs.odu.edu!Amiga-Request
  2. From: Amiga-Request@cs.odu.edu (Amiga Sources/Binaries Moderator)
  3. Newsgroups: comp.sources.amiga
  4. Subject: v90i191: app 2.0 - assembly pre-processor, Part01/01
  5. Message-ID: <13024@xanth.cs.odu.edu>
  6. Date: 2 Jul 90 23:36:50 GMT
  7. Sender: tadguy@cs.odu.edu
  8. Reply-To: karl@sugar.uucp
  9. Lines: 1139
  10. Approved: tadguy@cs.odu.edu (Tad Guy)
  11. X-Mail-Submissions-To: Amiga@cs.odu.edu
  12. X-Post-Discussions-To: comp.sys.amiga
  13.  
  14. Submitted-by: karl@sugar.uucp
  15. Posting-number: Volume 90, Issue 191
  16. Archive-name: util/app-2.0/part01
  17.  
  18. APP is a preprocessor for the 68000 assembler that comes with Aztec C for 
  19. the Amiga.   It will probably work with other 68000 assemblers.  It works
  20. fine with 68020/68030 instructions, too.  It can easily be adapted to 
  21. other processor architectures as well.
  22.  
  23. APP provides structured programming constructs for the assembly language
  24. programmer.  Specifically, APP provides support for IF-THEN-ELSE-ELSEIF-
  25. ENDIF constructs and for DO-WHILE-UNTIL-ENDDO constructs.  
  26.  
  27. #!/bin/sh
  28. # This is a shell archive.  Remove anything before this line, then unpack
  29. # it by saving it into a file and typing "sh file".  To overwrite existing
  30. # files, type "sh file -c".  You can also feed this as standard input via
  31. # unshar, or by typing "sh <file", e.g..  If this archive is complete, you
  32. # will see the following message at the end:
  33. #        "End of archive 1 (of 1)."
  34. # Contents:  README app.c app.pro app.uu makefile
  35. # Wrapped by tadguy@xanth on Mon Jul  2 19:35:50 1990
  36. PATH=/bin:/usr/bin:/usr/ucb ; export PATH
  37. if test -f 'README' -a "${1}" != "-c" ; then 
  38.   echo shar: Will not clobber existing file \"'README'\"
  39. else
  40. echo shar: Extracting \"'README'\" \(9396 characters\)
  41. sed "s/^X//" >'README' <<'END_OF_FILE'
  42. XAPP - Assembly Pre-Processor   
  43. X----------------------------
  44. X
  45. XVersion 2.0, 28-April-1990
  46. X
  47. XPUBLIC DOMAIN
  48. X
  49. Xwritten by Karl Lehenbauer, first release 12/8/88, with a lot of design 
  50. Xinput by Peter da Silva.
  51. X
  52. XVersion 2.0, released 4/28/90, incorporated changes by Brett Bourbin 
  53. X (Selgus Limited) involving input/output file handling and added the dbra 
  54. X looping construct.  Karl made a backwards-compatible version  of the new 
  55. X i/o file handling, converted to ANSI C, spruced up the docs, etc.
  56. X
  57. X
  58. XDisclaimer and Redistribution Information
  59. X-----------------------------------------
  60. X
  61. XAPP is placed freely into the public domain for any use without restriction.
  62. XAPP comes without warranties, expressed or implied.  This is free software.
  63. XWe don't have a contract.
  64. X
  65. XWe're not asking for money for this, but if you use it a lot, a check for
  66. X$10 or $20 would always be appreciated.  Make checks to Hackercorp, 3918 
  67. XPanorama, Missouri City, TX  77459
  68. X
  69. X
  70. XWhat it is
  71. X----------
  72. X
  73. XAPP is a preprocessor for the 68000 assembler that comes with Aztec C for 
  74. Xthe Amiga.   It will probably work with other 68000 assemblers.  It works
  75. Xfine with 68020/68030 instructions, too.  It can easily be adapted to 
  76. Xother processor architectures as well.
  77. X
  78. XAPP provides structured programming constructs for the assembly language
  79. Xprogrammer.  Specifically, APP provides support for IF-THEN-ELSE-ELSEIF-
  80. XENDIF constructs and for DO-WHILE-UNTIL-ENDDO constructs.  
  81. X
  82. XConsider the C pseudocode fragment:
  83. X
  84. Xlong a, b;
  85. X
  86. X    if (a < 0)
  87. X    {
  88. X        less_than_zero_stuff();
  89. X    }
  90. X    else
  91. X    {
  92. X        not_less_that_zero_stuff();
  93. X    }
  94. X
  95. XIn assembler (or pre-77 FORTRAN, for example) to do the same thing requires 
  96. Xthe creation of two bogus labels, as in:
  97. X
  98. X    move.l    _a,d0
  99. X    bge        else_part
  100. X    jsr        _less_than_zero_stuff
  101. X    bra        past_the_else
  102. Xelse_part
  103. X    jsr        _not_less_than_zero_stuff
  104. Xpast_the_else
  105. X
  106. XWhen you start nesting these deeply, the code quickly becomes unreadable.
  107. XNote also that you have to reverse the sense to branch around the code
  108. Xyou really want to execute.  This makes the code less clear.
  109. XIf the assembler had structured programming constructs like C, Modula 2,
  110. XForth, etc, the creation of these superfluous labels is unnecessary.
  111. XUsing APP, the above code fragment can be rewritten:
  112. X
  113. X    move.l    _a,d0
  114. X    .if    lt
  115. X    jsr        _less_than_zero_stuff
  116. X    .else
  117. X    jsr        _not_less_than_zero_stuff
  118. X    .endif
  119. X
  120. XTo define an "if", enter an opcode of ".if" and an operand of a condition
  121. Xcode that the assembler recognizes as a branch when following behind a 'b',
  122. Xas in condition codes "le", "lt", "eq", "ne", "gt", "ge" yielding "ble",
  123. X"blt", "beq", "bne", "bgt", "bge"  You will have issued instructions to
  124. Xset up the condition codes before the ".if".
  125. X
  126. XFor "if", APP will assemble a conditional branch with the sense reversed,
  127. Xbranching to the matching ".else", ".elseif", or ".endif".  APP will make
  128. Xup labels and produce the equivalent branching code as above.  I have chosen
  129. Xto make APP's labels be 'L' followed by an increasing sequential integer
  130. Xlabel number.  This was chosen to avoid conflicting with Manx's '.' followed
  131. Xby the number so you can incrementally "structurize" and test as you hand
  132. Xoptimize the output of cc with optimization and assembly source generation
  133. Xflags selected.
  134. X
  135. XAPP also supports a do/enddo construct.  The way it works is ".enddo"
  136. Xcompiles a "branch always" instruction back to the corresponding ".do".
  137. XTo exit the do/enddo, three constructs are provided.  These are ".while",
  138. X".until" and ".dbra".  ".while" takes a condition code and, if it is true,
  139. Xexecution continues below the while, else a branch past the enddo is
  140. Xtaken.  ".until" in the opposite manner, if the condition code is true
  141. Xa branch past the enddo is taken otherwise it isn't.  (".dbra" will be
  142. Xdescribed later below.)  For example,
  143. X
  144. X    .do
  145. X      ;conditional setup stuff
  146. X      .
  147. X      .
  148. X    .while ne
  149. X      ; execution stuff
  150. X      .
  151. X      .
  152. X    .enddo
  153. X
  154. X...will execute code between the do and the enddo until the condition code
  155. Xat the "while" isn't true anymore.  Multiple .whiles and .untils may be
  156. Xused and .whiles and .untils may be freely intermixed.
  157. X
  158. XAn additional do structure provided on the 68000 series to take advantage
  159. Xof specific 68000 looping capabilities.  This is the decrement-and-branch,
  160. XDBRA, instruction.  Using DBRA, many simple copying loops can be coded with
  161. Xonly two instructions.  Consequently, dbra is provided as a .do-terminating
  162. Xinstruction as an alternative to .enddo, as in:
  163. X
  164. X    .do
  165. X      ; loop code
  166. X      ;
  167. X    .dbra d5
  168. X
  169. XIn the preceding example, the loop code will be executed a number of times
  170. Xequal to the value in d5, with the dbra instruction decrementing d5 each 
  171. Xtime through the loop until d5 is zero when dbra checks it, at which time
  172. Xit will "fall through", executing the next instruction after the dbra.
  173. X
  174. XNote that .dbra is different from dbra in that .dbra indicates to app
  175. Xthat it terminates a matching .do, thus that app is to generate a dbra 
  176. Xinstruction to decrement the specified register and branch back to the 
  177. Xcorresponding .do statement, while a "dbra" is just a regular dbra 
  178. Xinstruction, app just passes it through, and it requires the register and
  179. Xa label like any other label-branching instruction on the 68000.
  180. X
  181. X
  182. XNesting of conditionals is permitted to a depth of 32.  When nesting, I
  183. Xreccommend indenting your code, as in:
  184. X
  185. X    tst.l    d0
  186. X    .if gt
  187. X        add.l    d0,d1
  188. X        cmp.l    #max,d1
  189. X        .if gt
  190. X            move.l    #max,d1
  191. X        .endif
  192. X    .endif
  193. X
  194. XSetting tab stops at four seems to work well.
  195. X
  196. X
  197. XHow To Invoke APP
  198. X-----------------
  199. X
  200. XAPP takes the name of the structured assembly source it is to compile
  201. Xinto standard assembly source code on the command line, as in
  202. X
  203. X    app foo.app
  204. X
  205. XThis produces foo.asm, if app doesn't detect any errors while processing 
  206. Xthe file.
  207. X
  208. XWhen used in the above manner, the name of the source file must end with 
  209. X.app, and app will always create the output file with a .asm extension.
  210. X
  211. XAlternatively, you may specify the output file, as in:
  212. X
  213. X    app -o foo.asm foo.a
  214. X
  215. XNote that for the second form, the .app extension of the source filename
  216. Xis not required.
  217. X
  218. X
  219. XIntegrating APP with your makefile
  220. X----------------------------------
  221. X
  222. XIf you add the following rules to your makefile and list object files
  223. Xcorresponding to your assembly preprocessor source .app files in your 
  224. Xmake dependencies, make will run APP over your .app files and then
  225. Xrun "as" over the resulting .asm files automatically.
  226. X
  227. X.app.o:
  228. X    app $*.app
  229. X    as $*.asm
  230. X
  231. X
  232. XCondition Codes Known by APP 
  233. X----------------------------
  234. X
  235. X    The following condition codes may be used APP's .if, .elseif, .while
  236. X    and .until statements:
  237. X
  238. X    "ne"
  239. X    "eq"
  240. X    "lt"
  241. X    "ge"
  242. X    "le"
  243. X    "gt"
  244. X    "cc"
  245. X    "cs"
  246. X    "vc"
  247. X    "vs"
  248. X    "hi"
  249. X    "ls"
  250. X    "pl"
  251. X    "mi"
  252. X
  253. XConsult your 68000 Reference Manual if you need to know
  254. Xwhat status register bits and states correspond to these 
  255. Xcodes.  They're the standard ones.
  256. X
  257. X
  258. XAPP Error Messages
  259. X------------------
  260. X
  261. XAPP does a lot of checking of your APP "dot" statements to insure their
  262. Xvalidity.  Specifically, APP insures that all .ifs have matching .endifs,
  263. Xthat all .dos have matching .enddo or .dbra, that only one .else is 
  264. Xspecified inside a .if, that .elseifs are only specified inside .ifs, 
  265. Xthat .whiles and .untils are only specified inside a .do and that all
  266. X"dot" structures are closed at end of file.  If APP does detect an error,
  267. Xit prints an error message including the line number and exits.  (It could
  268. Xconceivably go on, but I have yet to take it this far.)
  269. X
  270. XIf APP is pointing to the last line in the file, the problem is that you
  271. Xdidn't close a .if or .do structure somewhere earlier in the file.
  272. X
  273. XIf APP exits with an error, it removes the .asm output file so the file
  274. Xwon't confuse "make" into thinking everything went OK with APP when it 
  275. Xreally didn't.
  276. X
  277. X
  278. XEnumeration of Variations by Pseudo-Example
  279. X-------------------------------------------
  280. X
  281. X    .if cc
  282. X    .endif
  283. X
  284. X    .if cc
  285. X    .else
  286. X    .endif
  287. X
  288. X    .if cc
  289. X    .elseif cc
  290. X    .endif
  291. X
  292. X    .if cc
  293. X    .elseif cc
  294. X    .elseif cc
  295. X    .endif
  296. X
  297. X    .do
  298. X    .enddo
  299. X
  300. X    .do
  301. X    .while cc
  302. X    .enddo
  303. X
  304. X    .do
  305. X    .until cc
  306. X    .enddo
  307. X
  308. X    .do
  309. X    .until cc
  310. X    .until cc
  311. X    .while cc
  312. X    .enddo
  313. X
  314. X    .do
  315. X    .dbra reg
  316. X
  317. X    .do
  318. X    .until cc
  319. X    .while cc
  320. X    .dbra reg
  321. X
  322. X
  323. XMiscellaneous Notes
  324. X-------------------
  325. X
  326. XAPP conditionals may be nested up to 32 levels deep.  If you need to go
  327. Xdeeper (seven or eight seems like the realistic-use upper limit to me), 
  328. Xchange the MAX_NESTING_LEVELS define in app.c.
  329. X
  330. XAll the APP constructs must be entered in lower case only, and the condition
  331. Xcodes as well.
  332. X
  333. XNote that the functions provided by APP could have been done by assembler
  334. Xmacros if the Aztec assembler had supported the ability to expand a macro
  335. Xwith an argument being the *value* of a SET variable, had string variables 
  336. Xor the ability to concatenate text with a SET variable -- it doesn't, and
  337. Xsimilar problems appear in other assemblers as well.
  338. X
  339. XNote also that APP doesn't check condition codes for validity unless their
  340. Xsense has to be reversed.  It probably should check them, but invalid ones 
  341. Xwon't get past the assembler in any case.
  342. X
  343. XAPP is so vanilla in its construction that it should run on about any
  344. Xmachine with a C compiler and a stdio library.  It for sure runs under
  345. XAztec C on the Amiga and on Intel '286 Multibus Xenix (don't ask why).
  346. XVersion 1.1 and onward, though, require an ANSI standard C compiler.
  347. X
  348. XThe documentation was significantly more work than the code.
  349. X
  350. XWarm Regards,
  351. XKarl @ The Alternate Hacker's Haven -- Houston, TX, 12/11/88
  352. Xupdated - 4/28/90
  353. XUsenet: uunet!sugar!karl  Internet/BITNET: karl@sugar.hackercorp.com
  354. X
  355. END_OF_FILE
  356. if test 9396 -ne `wc -c <'README'`; then
  357.     echo shar: \"'README'\" unpacked with wrong size!
  358. fi
  359. # end of 'README'
  360. fi
  361. if test -f 'app.c' -a "${1}" != "-c" ; then 
  362.   echo shar: Will not clobber existing file \"'app.c'\"
  363. else
  364. echo shar: Extracting \"'app.c'\" \(9992 characters\)
  365. sed "s/^X//" >'app.c' <<'END_OF_FILE'
  366. X/* app.c - 68000 assembly pre-processor
  367. X *
  368. X * written by Karl Lehenbauer (uunet!sugar!karl or karl@sugar.hackercorp.com)
  369. X * original release Dec-08-1988
  370. X *
  371. X * PUBLIC DOMAIN -- no warranties of usefulness, suitabilitiy, correctness
  372. X *
  373. X * Jan-09-1990    Brett Bourbin (Selgus Limited) changed input/output file
  374. X *        handling, incorrect text strings and added the dbra construct.
  375. X *
  376. X * April-28-1990  Release 2.0
  377. X *  Rewrote filename-handling code to provide the -o option with backward
  378. X *   compatibility. Updated the docs plus converted to ANSI C.
  379. X */
  380. X
  381. X#include <stdio.h>
  382. X#include <assert.h>
  383. X
  384. X#include "app.pro"
  385. X
  386. X#define YES 1
  387. X#define NO 0
  388. X
  389. X#define MATCH 0
  390. X
  391. Xint current_nest_level = -1;
  392. Xint master_label_number = 0;
  393. Xunsigned int line_number = 0;
  394. X
  395. Xchar *label;
  396. Xchar *opcode;
  397. Xchar *operands;
  398. Xchar *comment;
  399. X
  400. Xchar *input_filename, *input_extension, *output_filename;
  401. X
  402. Xpanic(char *s)
  403. X{
  404. X    fprintf(stderr,"app: %s at line %d\n",s,line_number);
  405. X    fclose(stdout);
  406. X    unlink(output_filename);
  407. X    exit(1);
  408. X}
  409. X
  410. X/* given a pointer to a line, make the global character pointers "label",
  411. X * "opcode", "operands" and "comment" point to the various fields within
  412. X * the line, or NULL for any that aren't present.  Note that crackline
  413. X * butchers the line up by writing null bytes into it.
  414. X */
  415. Xcrackline(char *s)
  416. X{
  417. X    register char *p = s;
  418. X
  419. X    label = NULL;
  420. X    opcode = NULL;
  421. X    operands = NULL;
  422. X    comment = NULL;
  423. X
  424. X    /* suck up leading blanks */
  425. X    while ((*p == ' ') || (*p == '\t'))
  426. X        p++;
  427. X
  428. X    /* if end of line, return -- it's an empty line */
  429. X    if (*p == '\0')
  430. X        return;
  431. X
  432. X    /* if the first nonblank char is a semicolon, it's a comment */
  433. X    if (*p == ';')
  434. X    {
  435. X        comment = s;
  436. X        return;
  437. X    }
  438. X
  439. X    /* if the very first char isn't blank (and we already know it's
  440. X       not a semicolon), it's a label
  441. X     */
  442. X    if ((*s != ' ') && (*s != '\t'))
  443. X    {
  444. X        label = s;
  445. X        p = s + 1;
  446. X        while (*p != ' ' && *p != '\t' && *p != '\0') p++;
  447. X        if ((*p == ' ') || (*p == '\t'))
  448. X        {
  449. X            *p = '\0';
  450. X            p++;
  451. X        }
  452. X        else
  453. X            return;
  454. X    }
  455. X    else    /* there isn't a label, suck up spaces to next parm */
  456. X    {
  457. X        p = s;
  458. X        while ((*p == ' ' || *p == '\t')) p++;
  459. X        if (*p == '\0')
  460. X            return;
  461. X    }
  462. X
  463. X    /* if the next parm is a comment, assign and we're done */
  464. X    if (*p == ';')
  465. X    {
  466. X        comment = p;
  467. X        return;
  468. X    }
  469. X
  470. X    /* we're at the opcode, assign it and terminate with \0 if spaces
  471. X     * follow, else we're done */
  472. X    opcode = p;
  473. X    while (*p != ' ' && *p != '\t' && *p != '\0') p++;
  474. X    if ((*p == ' ') || (*p == '\t'))
  475. X    {
  476. X        *p = '\0';
  477. X        p++;
  478. X    }
  479. X    else
  480. X        return;
  481. X
  482. X    /* if the next parm is a comment, assign and we're done */
  483. X    if (*p == ';')
  484. X    {
  485. X        comment = p;
  486. X        return;
  487. X    }
  488. X
  489. X    operands = p;
  490. X    while (*p != ' ' && *p != '\t' && *p != '\0') p++;
  491. X    if ((*p == ' ') || (*p == '\t'))
  492. X    {
  493. X        *p = '\0';
  494. X        p++;
  495. X    }
  496. X    else
  497. X        return;
  498. X
  499. X    comment = p;
  500. X
  501. X}
  502. X
  503. X#ifdef DEBUG
  504. Xdumpit(void)
  505. X{
  506. X    printf("label: %s, opcode %s, operands %s, comment %s\n",label,opcode,operands,comment);
  507. X}
  508. X#endif
  509. X
  510. Xchar s[255], ssave[255];
  511. X
  512. X#define IF_STATEMENT_TYPE 1
  513. X#define ELSE_STATEMENT_TYPE 2
  514. X#define DO_STATEMENT_TYPE 3
  515. X
  516. X#define MAX_NESTING_LEVELS 32
  517. X
  518. Xstruct nesting_context
  519. X{
  520. X    int construct_type;
  521. X    int label_number;
  522. X    int second_label_number;
  523. X};
  524. X
  525. Xstruct nesting_context nesting_data[MAX_NESTING_LEVELS];
  526. X
  527. X/* push - push a nesting construct context, executed on .if and .do */
  528. Xpush(int new_construct_type,int label,int second_label)
  529. X{
  530. X    struct nesting_context *np;
  531. X
  532. X    if (++current_nest_level >= MAX_NESTING_LEVELS)
  533. X        panic("too many nesting levels");
  534. X
  535. X    np = &nesting_data[current_nest_level];
  536. X    np->construct_type = new_construct_type;
  537. X    np->label_number = label;
  538. X    np->second_label_number = second_label;
  539. X}
  540. X
  541. X/* pop - discard the top nesting context, checking for underflow
  542. X *  called when conditionals have been successfully closed
  543. X */
  544. Xpop(void)
  545. X{
  546. X    if (current_nest_level >= 0)
  547. X        --current_nest_level;
  548. X    else
  549. X        panic("'endif', 'enddo' or 'dbra' without a matching 'if' or 'do'");
  550. X}
  551. X
  552. X/* generate and return new label number */
  553. Xnewlabel(void)
  554. X{
  555. X    return(master_label_number++);
  556. X}
  557. X
  558. X/* structure in support of reversing the sense of conditionals */
  559. Xstruct condition_code_struct
  560. X{
  561. X    char *condition;
  562. X    char *reverse_condition;
  563. X};
  564. X
  565. X#define N_CONDITION_TYPES 14
  566. X
  567. Xstruct condition_code_struct condition_code_array[N_CONDITION_TYPES] =
  568. X{
  569. X    {"ne", "eq"},
  570. X    {"eq", "ne"},
  571. X    {"lt", "ge"},
  572. X    {"ge", "lt"},
  573. X    {"le", "gt"},
  574. X    {"gt", "le"},
  575. X    {"cc", "cs"},
  576. X    {"cs", "cc"},
  577. X    {"vc", "vs"},
  578. X    {"vs", "vc"},
  579. X    {"hi", "ls"},
  580. X    {"ls", "hi"},
  581. X    {"pl", "mi"},
  582. X    {"mi", "pl"},
  583. X};
  584. X
  585. X/* given a pointer to text containing a condition code, returns the 
  586. X * a pointer to text containing a condition with reverse sense of
  587. X * the one passed as an argument. Bombs if the sense doesn't make sense
  588. X */
  589. Xchar *reverse_sense_of(char *s)
  590. X{
  591. X    struct condition_code_struct *ccp;
  592. X    int i;
  593. X
  594. X    for (i = 0, ccp = condition_code_array; i < N_CONDITION_TYPES; i++, ccp++)
  595. X
  596. X        if (strcmp(s,ccp->condition) == MATCH)
  597. X            return(ccp->reverse_condition);
  598. X
  599. X    panic("invalid condition code in 'if', 'elseif', 'while' or 'until'");
  600. X}
  601. X
  602. X/* print the label name corresponding to the number specified, should be
  603. X * called in more places in the program where printf is used instead, so
  604. X * you have to change it in several places if you want to change what the
  605. X * labels look like
  606. X */
  607. Xprint_label(int i)
  608. X{
  609. X    printf("L%d\n",i);
  610. X}
  611. X
  612. X/* to prevent parsing every line, looks_promising is a quick hack to see
  613. X * if its a line we're interested in or not.  If the line doesn't have
  614. X * a period as the first non-space or tab char, it's not promising, so
  615. X * we don't crack the line with the full blown line parses.  This is a
  616. X * performance hack.
  617. X */
  618. Xlooks_promising(char *s)
  619. X{
  620. X    while (*s != '\0')
  621. X    {
  622. X        if (*s == '.')
  623. X            return(YES);
  624. X
  625. X        if (*s != ' ' && *s != '\t')
  626. X            return(NO);
  627. X
  628. X        s++;
  629. X    }
  630. X    return(NO);
  631. X}
  632. X
  633. Xusage()
  634. X{
  635. X    fprintf(stderr,"\nThis program converts high-level structured assembly code\n");
  636. X    fprintf(stderr,"into regular assembly code.  See the README file for details.\n\n");
  637. X    fprintf(stderr,"usage:  app [ -o outputfile] filename.app\n");
  638. X    fprintf(stderr," (if -o is not specified, .app extension is required\n");
  639. X    fprintf(stderr,"  and output will have a .asm extension).\n\n");
  640. X    fprintf(stderr,"Hackercorp, 3918 Panorama, Missouri City, TX 77459 USA\n");
  641. X    fprintf(stderr,"tel# 713-438-4964, Usenet: uunet!sugar!karl\n");
  642. X    fprintf(stderr,"Internet/BITNET: karl@sugar.hackercorp.com\n\n");
  643. X    exit(1);
  644. X}
  645. X
  646. Xint main(int argc,char *argv[])
  647. X{
  648. X    fprintf(stderr,"Hackercorp public domain 68000 assembly preprocessor 2.0 28-April-1990\n");
  649. X
  650. X    if (argc == 4)
  651. X    {
  652. X        if (strcmp(argv[1],"-o") != MATCH)
  653. X            usage();
  654. X
  655. X        output_filename = argv[2];
  656. X        input_filename = argv[3];
  657. X    }
  658. X    else if (argc == 2)
  659. X    {
  660. X        input_filename = argv[1];
  661. X        output_filename = NULL;
  662. X    }
  663. X    else
  664. X        usage();
  665. X
  666. X    if (!output_filename)
  667. X    {
  668. X        input_extension = input_filename + strlen(input_filename) - 4;
  669. X        if (strcmp(".app",input_extension) != MATCH)
  670. X            usage();
  671. X    }
  672. X
  673. X    if (freopen(input_filename,"r",stdin) == NULL)
  674. X    {
  675. X        perror(input_filename);
  676. X        exit(5);
  677. X    }
  678. X
  679. X    /* create output filename if necessary, by overwriting input name */
  680. X    if (!output_filename)
  681. X    {
  682. X        strcpy(input_extension,".asm");
  683. X        output_filename = input_filename;
  684. X    }
  685. X
  686. X    if (freopen(output_filename,"w",stdout) == NULL)
  687. X    {
  688. X        perror(output_filename);
  689. X        exit(5);
  690. X    }
  691. X
  692. X    preprocess_file();
  693. X    return(0);
  694. X}
  695. X
  696. Xpreprocess_file(void)
  697. X{
  698. X    struct nesting_context *np;
  699. X    int i;
  700. X
  701. X    /* for all lines in the file */
  702. X    while (gets(s) != NULL)
  703. X    {
  704. X        line_number++;    /* count the line */
  705. X
  706. X        /* if it's not promising, copy it to output and go on */
  707. X        if (!looks_promising(s))
  708. X        {
  709. X            printf("%s\n",s);
  710. X            goto more;
  711. X        }
  712. X
  713. X        strcpy(ssave,s);
  714. X        crackline(s);
  715. X
  716. X        if (strcmp(opcode,".if") == MATCH)
  717. X        {
  718. X            printf("\tb%s\tL%d\n",reverse_sense_of(operands),i = newlabel());
  719. X            push(IF_STATEMENT_TYPE,i,-1);
  720. X        }
  721. X        else if (strcmp(opcode,".else") == MATCH)
  722. X        {
  723. X            np = &nesting_data[current_nest_level];
  724. X
  725. X            if (np->construct_type != IF_STATEMENT_TYPE)
  726. X                panic("'else' without 'if'");
  727. X
  728. X            printf("\tbra\tL%d\n",i = newlabel());
  729. X            /* print the label from the top context */
  730. X            print_label(np->label_number);
  731. X            np->label_number = i;
  732. X            np->construct_type = ELSE_STATEMENT_TYPE;
  733. X        }
  734. X        else if (strcmp(opcode,".endif") == MATCH)
  735. X        {
  736. X            np = &nesting_data[current_nest_level];
  737. X
  738. X            if ((np->construct_type != IF_STATEMENT_TYPE)
  739. X              && (np->construct_type != ELSE_STATEMENT_TYPE))
  740. X                panic("'endif' without 'if' or 'else'");
  741. X
  742. X            print_label(np->label_number);
  743. X            pop();
  744. X        }
  745. X        else if (strcmp(opcode,".elseif") == MATCH)
  746. X        {
  747. X            np = &nesting_data[current_nest_level];
  748. X
  749. X            if (np->construct_type != IF_STATEMENT_TYPE)
  750. X                panic("'else' without 'if'");
  751. X
  752. X            printf("\tbra\tL%d\n",i = newlabel());
  753. X            /* print the label from the top context */
  754. X            print_label(np->label_number);
  755. X            np->label_number = i;
  756. X            printf("\tb%s\tL%d\n",reverse_sense_of(operands),i);
  757. X        }
  758. X        else if (strcmp(opcode,".do") == MATCH)
  759. X        {
  760. X            print_label(i = newlabel());
  761. X            push(DO_STATEMENT_TYPE,i,newlabel());
  762. X        }
  763. X        else if (strcmp(opcode,".while") == MATCH)
  764. X        {
  765. X            np = &nesting_data[current_nest_level];
  766. X
  767. X            if (np->construct_type != DO_STATEMENT_TYPE)
  768. X                panic("'while' without 'do'");
  769. X
  770. X            printf("\tb%s\tL%d\n",reverse_sense_of(operands),np->second_label_number);
  771. X        }
  772. X        else if (strcmp(opcode,".enddo") == MATCH)
  773. X        {
  774. X            np = &nesting_data[current_nest_level];
  775. X
  776. X            if (np->construct_type != DO_STATEMENT_TYPE)
  777. X                panic("'enddo' without 'do'");
  778. X
  779. X            printf("\tbra\tL%d\n",np->label_number);
  780. X            print_label(np->second_label_number);
  781. X            pop();
  782. X
  783. X        }
  784. X        else if (strcmp(opcode,".dbra") == MATCH)
  785. X        {
  786. X            np = &nesting_data[current_nest_level];
  787. X
  788. X            if (np->construct_type != DO_STATEMENT_TYPE)
  789. X                panic("'dbra' without 'do'");
  790. X
  791. X            printf("\tdbra\t%s,L%d\n",operands,np->label_number);
  792. X            print_label(np->second_label_number);
  793. X            pop();
  794. X
  795. X        }
  796. X        else if (strcmp(opcode,".until") == MATCH)
  797. X        {
  798. X            np = &nesting_data[current_nest_level];
  799. X
  800. X            if (np->construct_type != DO_STATEMENT_TYPE)
  801. X                panic("'until' without 'do'");
  802. X
  803. X            printf("\tb%s\tL%d\n",operands,np->second_label_number);
  804. X        }
  805. X        else
  806. X            printf("%s\n",ssave);
  807. X    more: ;
  808. X    }
  809. X    if (current_nest_level >= 0)
  810. X        panic("didn't close all your control structures");
  811. X}
  812. X
  813. END_OF_FILE
  814. if test 9992 -ne `wc -c <'app.c'`; then
  815.     echo shar: \"'app.c'\" unpacked with wrong size!
  816. fi
  817. # end of 'app.c'
  818. fi
  819. if test -f 'app.pro' -a "${1}" != "-c" ; then 
  820.   echo shar: Will not clobber existing file \"'app.pro'\"
  821. else
  822. echo shar: Extracting \"'app.pro'\" \(318 characters\)
  823. sed "s/^X//" >'app.pro' <<'END_OF_FILE'
  824. X/* app.c */
  825. Xint panic(char *s);
  826. Xint crackline(char *s);
  827. Xint push(int new_construct_type, int label, int second_label);
  828. Xint pop(void);
  829. Xint newlabel(void);
  830. Xchar *reverse_sense_of(char *s);
  831. Xint print_label(int i);
  832. Xint looks_promising(char *s);
  833. Xint usage(void);
  834. Xint main(int argc, char **argv);
  835. Xint preprocess_file(void);
  836. END_OF_FILE
  837. if test 318 -ne `wc -c <'app.pro'`; then
  838.     echo shar: \"'app.pro'\" unpacked with wrong size!
  839. fi
  840. # end of 'app.pro'
  841. fi
  842. if test -f 'app.uu' -a "${1}" != "-c" ; then 
  843.   echo shar: Will not clobber existing file \"'app.uu'\"
  844. else
  845. echo shar: Extracting \"'app.uu'\" \(15581 characters\)
  846. sed "s/^X//" >'app.uu' <<'END_OF_FILE'
  847. Xbegin 644 app
  848. XM```#\P`````````#``````````(```FK```!X@````$```/I```)JT[Z$%PO6
  849. XM+(`*+R\`"$AZ!Q9(;('\3KH*X$AL@>9.NA]*+RR#DDZZ(OQ(>``!3KHD2D_OU
  850. XM`!Q.=4CG`#`F;P`,)$M"K(.60JR#FD*L@YY"K(.B#!(`(&<&#!(`"68$4HI@Z
  851. XM\$H29@9,WPP`3G4,$@`[9@8I2X.B8.X,$P`@9S@,$P`)9S(I2X.6)$M2B@P2S
  852. XM`"!G#@P2``EG"$H29P12BF#L#!(`(&<&#!(`"68&0A)2BF`"8+)@&"1+#!(`!
  853. XM(&<&#!(`"68$4HI@\$H29@)@F`P2`#MF!BE*@Z)@C"E*@YH,$@`@9PX,$@`)Y
  854. XM9PA*$F<$4HI@[`P2`"!G!@P2``EF!D(24HI@!&``_V`,$@`[9@@I2H.B8`#_M
  855. XM4BE*@YX,$@`@9PX,$@`)9PA*$F<$4HI@[`P2`"!G!@P2``EF!D(24HI@!&``0
  856. XM_R0I2H.B8`#_'$CG`"!2K(`"#*P````@@`)M"DAZ!=I.NOZB6$\@+(`"(@#C9
  857. XMB-"!Y8A![(.FT(@D0"2O``@E;P`,``0E;P`0``A,WP0`3G5*K(`";093K(`"A
  858. XM8`I(>@6R3KK^8EA/3G4@+(`&4JR`!DYU2.<@('0`0>R`#B1(8"(O$B\O`!!.7
  859. XMNA4P2H!03V8*("H`!$S?!`1.=2`"4H(@2E"*#((````.;=9(>@7&3KK^%%A/#
  860. XM8-XO+P`$2'H%\TZZ"KA03TYU2.<`("1O``A*$F<B#!(`+F8(<`%,WP0`3G4,^
  861. XM$@`@9PH,$@`)9P1P`&#J4HI@VG``8.)(>@6Z2&R!_$ZZ"+1(>@7J2&R!_$ZZ7
  862. XM"*A(>@8>2&R!_$ZZ")Q(>@8]2&R!_$ZZ")!(>@9G2&R!_$ZZ"(1(>@:'2&R!!
  863. XM_$ZZ"'A(>@:S2&R!_$ZZ"&Q/[P`X2'H&T$AL@?Q.N@A<2'@``4ZZ(=9/[P`,A
  864. XM3G5(YR`@)"\`#"1O`!!(>@;72&R!_$ZZ"#8,@@````103V8D2'H'"2\J``1."
  865. XMNA0B2H!03V<$3KK_6"EJ``B#DBEJ``R%)F`8#((````"9@PI:@`$A29"K(.2<
  866. XM8`1.NO\R2JR#DF8P+RR%)DZZ&AC0K(4F*4"%*@:L_____(4J+RR%*DAZ!JY.E
  867. XMNA/(2H!/[P`,9P1.NO[\2&R!T$AZ!ILO+(4F3KH'T$J`3^\`#&82+RR%)DZZ]
  868. XM"&1(>``%3KHA%%!/2JR#DF842'H&<2\LA2I.NAZH*6R%)H.24$](;('F2'H&Z
  869. XM7B\L@Y).N@>,2H!/[P`,9A(O+(.23KH(($AX``5.NB#04$]A"'``3-\$!$YU`
  870. XM2.<@($ALA2Y.N@>82H!83V<``T92K(`*2&R%+DZZ_C)*@%A/9A)(;(4N2'H&=
  871. XM!DZZ"-)03V```QY(;(4N2&R&+4ZZ'BA(;(4N3KK\-DAZ!>@O+(.:3KH2[$J`\
  872. XM3^\`%&8R3KK]D"0`+P`O+(.>3KK]CEA/+P!(>@7$3KH(B$AX__\O`DAX``%.8
  873. XMNOT,3^\`&&```L1(>@6P+RR#FDZZ$J9*@%!/9E`@+(`"(@#CB-"!Y8A![(.F\
  874. XMT(@D0`R2`````6<*2'H%B$ZZ^XA83TZZ_28D`"\`2'H%BDZZ""HO*@`$3KK]X
  875. XM8"5"``0DO`````)/[P`,8``"8DAZ!7(O+(.:3KH21$J`4$]F0"`L@`(B`..(T
  876. XMT('EB$'L@Z;0B"1`#)(````!9Q(,D@````)G"DAZ!4-.NOL>6$\O*@`$3KK]M
  877. XM!DZZ_)Q83V```A!(>@5&+RR#FDZZ$?)*@%!/9F`@+(`"(@#CB-"!Y8A![(.FM
  878. XMT(@D0`R2`````6<*2'H$U$ZZ^M183TZZ_'(D`"\`2'H$UDZZ!W8O*@`$3KK\N
  879. XMK"5"``0O`B\L@YY.NOQ:6$\O`$AZ!)!.N@=43^\`&&```9Y(>@3<+RR#FDZZH
  880. XM$8!*@%!/9B1.NOPF)``O`$ZZ_&Q.NOP:+P`O`DAX``-.NONP3^\`$&```6A($
  881. XM>@2J+RR#FDZZ$4I*@%!/9D8@+(`"(@#CB-"!Y8A![(.FT(@D0`R2`````V<*5
  882. XM2'H$@TZZ^BQ83R\J``@O+(.>3KK[S%A/+P!(>@0"3KH&QD_O``Q@``$02'H$]
  883. XM;B\L@YI.NA#R2H!03V9&("R``B(`XXC0@>6(0>R#IM"()$`,D@````-G"DAZ$
  884. XM!$=.NOG46$\O*@`$2'H#VDZZ!GHO*@`(3KK[L$ZZ^T9/[P`,8```N$AZ!#(OQ
  885. XM+(.:3KH0FDJ`4$]F2"`L@`(B`..(T('EB$'L@Z;0B"1`#)(````#9PI(>@0*?
  886. XM3KKY?%A/+RH`!"\L@YY(>@0,3KH&'B\J``A.NOM43KKZZD_O`!!@7$AZ!``O>
  887. XM+(.:3KH00$J`4$]F/"`L@`(B`..(T('EB$'L@Z;0B"1`#)(````#9PI(>@/9'
  888. XM3KKY(EA/+RH`""\L@YY(>@,`3KH%Q$_O``Q@#DALABU(>@+F3KH%LE!/8`#\`
  889. XMKDJL@`)M"DAZ`[9.NOCJ6$],WP0$3G5A<'`Z("5S(&%T(&QI;F4@)60*`'1OE
  890. XM;R!M86YY(&YE<W1I;F<@;&5V96QS`"=E;F1I9B<L("=E;F1D;R<@;W(@)V1B-
  891. XM<F$G('=I=&AO=70@82!M871C:&EN9R`G:68G(&]R("=D;R<`;F4`97$`;'0`B
  892. XM9V4`;&4`9W0`8V,`8W,`=F,`=G,`:&D`<&P`;6D`:6YV86QI9"!C;VYD:71I*
  893. XM;VX@8V]D92!I;B`G:68G+"`G96QS96EF)RP@)W=H:6QE)R!O<B`G=6YT:6PGL
  894. XM`$PE9`H`"E1H:7,@<')O9W)A;2!C;VYV97)T<R!H:6=H+6QE=F5L('-T<G5C#
  895. XM='5R960@87-S96UB;'D@8V]D90H`:6YT;R!R96=U;&%R(&%S<V5M8FQY(&-OG
  896. XM9&4N("!3964@=&AE(%)%041-12!F:6QE(&9O<B!D971A:6QS+@H*`'5S86=E'
  897. XM.B`@87!P(%L@+6\@;W5T<'5T9FEL95T@9FEL96YA;64N87!P"@`@*&EF("UOM
  898. XM(&ES(&YO="!S<&5C:69I960L("YA<'`@97AT96YS:6]N(&ES(')E<75I<F5DN
  899. XM"@`@(&%N9"!O=71P=70@=VEL;"!H879E(&$@+F%S;2!E>'1E;G-I;VXI+@H*B
  900. XM`$AA8VME<F-O<G`L(#,Y,3@@4&%N;W)A;6$L($UI<W-O=7)I($-I='DL(%18*
  901. XM(#<W-#4Y(%5300H`=&5L(R`W,3,M-#,X+30Y-C0L(%5S96YE=#H@=75N970AB
  902. XM<W5G87(A:V%R;`H`26YT97)N970O0DE43D54.B!K87)L0'-U9V%R+FAA8VME%
  903. XM<F-O<G`N8V]M"@H`2&%C:V5R8V]R<"!P=6)L:6,@9&]M86EN(#8X,#`P(&%SR
  904. XM<V5M8FQY('!R97!R;V-E<W-O<B`R+C`@,C@M07!R:6PM,3DY,`H`+6\`+F%P7
  905. XM<`!R`"YA<VT`=P`E<PH`+FEF``EB)7,)3"5D"@`N96QS90`G96QS92<@=VET4
  906. XM:&]U="`G:68G``EB<F$)3"5D"@`N96YD:68`)V5N9&EF)R!W:71H;W5T("=I/
  907. XM9B<@;W(@)V5L<V4G`"YE;'-E:68`+F1O`"YW:&EL90`G=VAI;&4G('=I=&AO%
  908. XM=70@)V1O)P`N96YD9&\`)V5N9&1O)R!W:71H;W5T("=D;R<`+F1B<F$`)V1BC
  909. XM<F$G('=I=&AO=70@)V1O)P`)9&)R80DE<RQ,)60*`"YU;G1I;``G=6YT:6PG1
  910. XM('=I=&AO=70@)V1O)P!D:61N)W0@8VQO<V4@86QL('EO=7(@8V]N=')O;"!SA
  911. XM=')U8W1U<F5S``!(YR`@0>\`%"1(+PHO+P`4+R\`%$ZZ#3PD`"`"3^\`#$S?Y
  912. XM!`1.=4CG`"`D;P`0(`IG!DIJ``QF"'``3-\$`$YU+PI.NA0N0FH`#$AX__\O,
  913. XM"B\O`!@O+P`83KH"<D_O`!1@V$CG(#`F;P`0)$L@;('0L>R!U&0.(&R!T%*LK
  914. XM@=!P`!`08`I(;('03KH!7EA/)``,@/____]G$`R"````"F<(%((@2E**8,0,4
  915. XM@O____]F%+7+9P@(+``!@=UF"'``3-\,!$YU0A(@"V#T2.<`("1O``@@"F<>"
  916. XM2A)G&DAL@?PO"DZZ`)9(;('\2'H`2$ZZ`(I/[P`0+RR'+$ZZ!#(D0$J`6$]G(
  917. XM*$H29R1(;('\+RR'+$ZZ!!I83R\`3KH`7DAL@?Q(>``*3KH`$$_O`!!,WP0``
  918. XM3G4Z(```2.<@("0O``PD;P`0(`IG!DIJ``QF"'#_3-\$!$YU(%*QZ@`$9`P@9
  919. XM4E*2$()P`!`"8.9P`!`"+P`O"DZZ$5I03V#62.<@,"9O`!`D;P`48#0@4K'JN
  920. XM``1D#"!24I(0@G``$`)@#G``$`(O`"\*3KH1*%!/#(#_____9@AP_TS?#`1.$
  921. XM=5*+%!-FR'``8/!(YR`@0>\`$"1(+PHO+P`02&R!YDZZ"WHD`"`"3^\`#$S?,
  922. XM!`1.=4CG,#`D;P`4(`IG%G``,"H`#"8`9PP(`P`*9@8(`P`#9PAP_TS?#`Q.5
  923. XM=2!2L>H`!&4``*9*J@`(9@@O"DZZ$\)83S`J``P"0`"@9S!![('0)DAP`#`K.
  924. XM``P"@```0"`,@```0"!F""\+3KH/]EA/U_P````60>R#B+?(9=8@2M'\````(
  925. XM##`0`D"O_S"`+RH`$"\J``@0*@`.2(!(P"\`3KH(X"0`3^\`#&X@2H)F!'`"1
  926. XM8`)P!"!*T?P````,<@`R$("!,(!P_V``_UPDJ@`(($+1Z@`()4@`!"!24I)P:
  927. XM`!`08`#_0DCG/#(L;P`@)&\`)"9O`"@H+P`L)CP```0`$!)(@$C`*@`,@```>
  928. XM`')F#B0\```0`"8\```"`&`H#(4```!W9@@D/```$P%@&`R%````868()#P`D
  929. XM`!D!8`AP`$S?3#Q.=5**$!)(@`Q``"MF#!`J``%(@`Q``&)G#!`22(`,0`!B3
  930. XM9@I2B@C#``0(@@`,$!)(@`Q``"MF&B`""(```"0`",(``2`#`H#___G_)@`(T
  931. XMPP`+(`YG#"\"+PY.N@8.*`!03TJ$;90,A````!1LC!=$``XW0P`,(`M@@DCG6
  932. XM`"!![('0)$A*:@`,9QC5_````!9![(.(M<AF"'``3-\$`$YU8.)":@`40I)"-
  933. XMJ@`$0JH`""`*8.8`3F\@<W5C:"!F:6QE(&]R(&1I<F5C=&]R>0!!<F<@;&ES:
  934. XM="!T;V\@;&]N9P!"860@9FEL92!D97-C<FEP=&]R`$YO="!E;F]U9V@@;65M2
  935. XM;W)Y`$9I;&4@97AI<W1S`$EN=F%L:60@87)G=6UE;G0`1FEL92!T86)L92!O;
  936. XM=F5R9FQO=P!4;V\@;6%N>2!O<&5N(&9I;&5S`$YO="!A(&-O;G-O;&4`4&5R]
  937. XM;6ES<VEO;B!D96YI960`22]/(&5R<F]R`$YO('-P86-E(&QE9G0@;VX@9&5VL
  938. XM:6-E`%)E<W5L="!T;V\@;&%R9V4`07)G=6UE;G0@;W5T(&]F(&1O;6%I;@!%:
  939. XM>&5C(&9O<FUA="!E<G)O<@!296%D+6]N;'D@9FEL92!S>7-T96T`0W)O<W,M:
  940. XM9&5V:6-E(')E;F%M90!.;W1H:6YG('1O(')E860`2.<@`"0O``A*@FT:#((`I
  941. XM```2;A(@`N6`0>R`?B`P"`!,WP`$3G5!^@`&(`A@\E5N:VYO=VX@97)R;W(`#
  942. XM*D]A<D/L@Y)%[(.2M<EF#C(\`/UK"'0`(L)1R?_\*4^',"QX``0I3H<T2.>`+
  943. XM@`@N``0!*6<02_H`"$ZN_^)@!D*G\U].<T/Z`").KOYH*4"'.&8,+CP``X`'V
  944. XM3J[_E&`&*D].N@`:4$].=61O<RYL:6)R87)Y`$GY``!__DYU2.<`($CG``(B_
  945. XM/``!```P+(.(P?P`!BQLAS1.KO\Z3-]``"E`ASQF'DCG`0:;S2X\``$``"QLK
  946. XMAS1.KO^43-]@@"YLAS!.=2!LASQ":``$(&R'/#%\``$`$"!LASPQ?``!``H@:
  947. XM;(<P("R',)"H``10@"E`AT`@;(=`(+Q-04Y82.<``I/)+&R'-$ZN_MI,WT``D
  948. XM)$!*J@"L9SPO+P`,+R\`#"\*3KH!#"E\`````8=$(&R'/%B(,!``0(``,(`@Y
  949. XM;(<\T?P````*,!``0(``,(!/[P`,8&I(YP`"($K1_````%PL;(<T3J[^@$S?&
  950. XM0`!(YP`"($K1_````%PL;(<T3J[^C$S?0``I0(=((&R'2$JH`"1G)DCG``(@/
  951. XM;(=((&@`)"(0+&R'.$ZN_X),WT``+RR'2"\*3KH%#%!/*6R'2(=,2.<``BQLS
  952. XMASA.KO_*3-]``"!LASP@@$CG``(L;(<X3J[_Q$S?0``@;(<\(4``!F<D2.<@@
  953. XM`B0\```#[4'Z`#0B""QLASA.KO_B3-]`!"!LASPA0``,+RR'3"\LAU!.NO`R4
  954. XM4$\O`$ZZ$?A83TS?!`!.=2H`2.<X,B8O`!PH+P`@)F\`)"!#2J@`K&<4($,@;
  955. XM*`"LY8`L0"`N`!#E@"1`8`0D;(.*$!)(@$C`T(14@"E`AU1(YP`"<@`@+(=4U
  956. XM+&R'-$ZN_SI,WT``*4"'6&8&3-],'$YU$!)(@$C`)``O`B!*4H@O""\LAUA.'
  957. XMN@462'H!2B!"T>R'6"\(3KH/#B\$+PLO+(=83KH!-"!LAUA","@`*7P````!+
  958. XMAU`D0M7LAUA2BB9*3^\`(!`22(!(P"0`#(`````@9R`,@@````EG&`R"````T
  959. XM#&<0#((````-9P@,@@````IF!%**8,P,$@`@;78,$@`B9BI2BA`:2(!(P"0`"
  960. XM9QP6P@R"````(F80#!(`(F8$4HI@!D(K__]@`F#:8#@0&DB`2,`D`&<L#((`+
  961. XM```@9R0,@@````EG'`R"````#&<4#((````-9PP,@@````IG!!;"8,I"&TJ"6
  962. XM9@)3BE*LAU!@`/]20A-(YP`"<@`@+(=0Y8!8@"QLAS1.KO\Z3-]``"E`ATQFX
  963. XM"$*LAU!@`/[0=``D;(=88!H@`N6`(&R'3"&*"``O"DZZ"/S5P%**6$]2@K2L"
  964. XMAU!MX"`"Y8`@;(=,0K`(`&``_I@@`$SO`P``!"`((B\`#$H89OQ3B!#95\G_(
  965. XM_`2!``$``&KR0B!.=2\O``A(>`,!+R\`#&$&3^\`#$YU2.<^,BQO`"0H+P`HH
  966. XM3KH/;"9LASQT`&`0<@8@`DZZ$>!*LP@`9Q!2@C!L@XBQPF[H=@A@``%."`0`(
  967. XM"6=>2.<@`G3_(B\`!"QLASA.KO^L3-]`!"H`9T1(YP`"(@4L;(<X3J[_IDS?D
  968. XM0`!(YP`"(A<L;(<X3J[_N$S?0`!*@&8<2.<``BQLASA.KO]\3-]``"8`#(``'
  969. XM``#-9@``ZDCG(`(D/````^TB+P`$+&R'.$ZN_^),WT`$)$`@"F8``*0(!``(B
  970. XM9@9V`6```+Q(YR`")#P```/N(B\`!"QLASA.KO_B3-]`!"1`2H!F%DCG``(L@
  971. XM;(<X3J[_?$S?0``F`&```(9(YP`"<"%#^@#`+&R'-$ZN_=A,WT``+`!G%$CG]
  972. XM``(B1BQLAS1.KOYB3-]``&`P2.<P`G8!0?H`GB0((@HL;(<X3J[_T$S?0`Q(^
  973. XMYS`"=O]T`"(*+&R'.$ZN_[Y,WT`,8#`@!`*````%``R````%`&8@2.<``B(*D
  974. XM+&R'.$ZN_]Q,WT``=@4I0X<L</],WTQ\3G5R!B`"3KH0:B>*"`!R!B`"3KH0?
  975. XM7C>$"`0(!``+9Q9(YS`"=@%T`"(*+&R'.$ZN_[Y,WT`,(`)@PF1O<RYL:6)R9
  976. XM87)Y````2.<P("0O`!!.N@V<<@8@`DZZ$!@D0-7LASQ*@FT,,&R#B+'";P1*M
  977. XMDF80*7P````#ARQP_TS?!`Q.=3`J``1(P`*``````PR``````68,*7P````&E
  978. XMARQP_V#:2.<P`B8O`"0D+P`@(A(L;(<X3J[_UDS?0`PF``R`_____V882.<`7
  979. XM`BQLASA.KO]\3-]``"E`ARQP_V">(`-@FDSO`P``!+/(9PQP`!`8L!E6R/_Z)
  980. XM9@1P`$YU8P1P`4YU</].=4CG,#(L;P`82.<``G``0_H`UBQLAS1.KOW83-]`Q
  981. XM`"E`AUQF!DS?3`Q.=4CG``(@;P`@(&@`)"!H``0L;(=<3J[_LDS?0``D0$J`7
  982. XM9WY(YP`"0_H`H2!J`#8L;(=<3J[_H$S?0``D`&=02.<@`B0\```#[2(7+&R')
  983. XM.$ZN_^),WT`$)D!*@&<R(`OE@"8`($,M:``(`*0M2P"<2.<@`B0\```#[4'Z7
  984. XM`%8B""QLASA.KO_B3-]`!"U``*!(YP`"($HL;(=<3J[_IDS?0`!(YP`"(FR'8
  985. XM7"QLAS1.KOYB3-]``$*LAUQ@`/]`:6-O;BYL:6)R87)Y`%=)3D1/5P`J`$SOO
  986. XM`P``!"`((B\`#&`"$-E7R?_\9PP$@0`!``!J\$YU0AA1R?_\!($``0``:O).G
  987. XM=4Y5_?1(YS\R)FT`""QM`!!^`"1M``P6$F8*(`=,WTS\3EU.=5**#`,`)6="A
  988. XM)`<@4['K``1D#"!34I,0@W``$`-@#G``$`,O`"\+3KH%+E!/#(#_____9P`$#
  989. XM9%*"%A)F!"`"8+A2B@P#`"5FPBX">``K?````"#__!8:<``0`V!F",0``&#R]
  990. XM",0``6#L",0``F#F",0``V#@6(XD+O_\2H)L!@C$``!$@A8:8%8K?````##_[
  991. XM_'0`8!@@`N>`<@`2`]"!T(+0@B0`!((````P%AIP`!`#0>R`SQ`P``!(@`@`&
  992. XM``)FU&`<!$``(&>@5T!GHE]`9Z130&>.54!GA%=`9ZQ@LBM"__@D/```?<8,$
  993. XM`P`N9EP6&@P#`"IF%%B.)"[__$J";`8D/```?<86&F`P=`!@&"`"YX!R`!(#F
  994. XMT('0@M"")``$@@```#`6&G``$`-![(#/$#```$B`"````F;4#((``'W&9P@KU
  995. XM?````"#__"H"#`,`:&8&",0`!V`6#`,`;&8&",0`!F`*#`,`3&8&",0`"!8:=
  996. XM*TH`#'``$`-@``&.8``#&@@$``=G"EB.(&[__#"'8!@(!``&9PI8CB!N__P@D
  997. XMAV`(6(X@;O_\((=T`&```:A8CB1N__PO"DZZ`P@D``R%``!]QEA/9P:TA6\"W
  998. XM)`5@``&&6(X6+O__0>W]^"1($(-T`6```7)T"&`0`$0`2'9X=!!@!@C$``1TV
  999. XM"@P#`%AF"$'Z`IX@"&`&0?H"IR`(*T#]]`@$``9G"%B.+"[__&`4"`0`!&<(?
  1000. XM6(XL+O_\8`98CBPN__P(!``$9PI*AFP&1(8(Q``%0>W_^"1(#(4``'W&9@)Z!
  1001. XM`4J&9@1*A6<<(@(@!DZZ!:P@;?WT%3`(`"("(`9.N@6H+`!FY$'M__B1RB0(\
  1002. XM"`0``V=N#`,`;V842H)G"@P2`#!G"+2%;00J`E*%8%0,`P!X9P8,`P!89DA**
  1003. XM@F=$#!(`,&<^M(5L$$'M_?JQRF0(%3P`,%*"8.P(!```9AP,K0```##__&82L
  1004. XM(`)4@+"M__AL""HM__A5A6#*%0,5/``P5(*TA6P00>W]^+'*9`@5/``P4H)@S
  1005. XM[&!,!$``)6<`_L@$0``S9P#^V`1```MG`/ZR4T!G`/[.6T!G`/[(6T!G`/Y0F
  1006. XM4T!G`/ZN4T!G`/ZL5T!G`/YL54!G`/ZN5T!G`/Z@8`#^*@@$``1G*`@$``5G5
  1007. XM!A4\`"U@&@@$``%G!A4\`"M@#@@$``)G!A4\`"!@`E."4H+>@@@$``!F``"0[
  1008. XM#*T````P__QF0@@$``1G/#`$`D``)F<T(%.QZP`$9`X@4U*3$)IP`!`J__]@%
  1009. XM#G``$!HO`"\+3KH!DE!/#(#_____9P``R%.M__A3@F`T(%.QZP`$9!`@4U*3!
  1010. XM$*W__W``$"W__V`0<``0+?__+P`O"TZZ`5A03PR`_____V<``(Y2AR`M__A37
  1011. XMK?_XL()NP"H"(`)3@DJ`9RX@4['K``1D#B!34I,0FG``$"K__V`.<``0&B\`L
  1012. XM+PM.N@$24$\,@/____]G2&#*"`0``&<\)`5@+"!3L>L`!&0.(%-2DQ"\`"!PR
  1013. XM`'`@8`Q(>``@+PM.N@#<4$\,@/____]G$E*'("W_^%.M__BP@F[(8`#[6'#_X
  1014. XM8`#[7#`Q,C,T-38W.#E!0D-$148`,#$R,S0U-C<X.6%B8V1E9@`@;P`$(`A*`
  1015. XM&&;\4TB1P"`(3G5(YP`@)&\`""`*9D1![('0)$A*:@`,9R8P*@`,`D`""&8<Z
  1016. XM2'C__R\*3KH`6@R`_____U!/9@AP_TS?!`!.==7\````%D'L@XBUR&7&<`!@F
  1017. XMZ$AX__\O"DZZ`"Q03V#:2.<`($'L@=`D2"\*3KH!OEA/U?P````60>R#B+7(H
  1018. XM9>I,WP0`3G5(YSP@)&\`&"@O`!P@"F<``9`T*@`,9P`!B`@"``EF``&`"`(`J
  1019. XM`V8``7@@2M'\````##`0`D#O_3"`2JH`"&8<#(3_____9@AP`$S?!#Q.=2\*2
  1020. XM3KH"R#0J``Q83P@"``YF-"!2L>H`"&,>2'@``2`2D*H`!"\`$"H`#DB`2,`O2
  1021. XM`$ZZ!$Q/[P`,)*H`""!J`!#1TB5(``0,A/____]F!'8`8`(6!"`2D*H`""H`L
  1022. XM,`("0`"@9TX,A/____]G(B!24I(0@R!*T?P````,,!`(P``.,(`T`$'Z_P0IK
  1023. XM2(=@4H4,A/____]G#`P#``IG!KJJ`!!E!'C_8`PE4@`$<``0`V``_TH(`@`.*
  1024. XM9S!*A6<<+P4O*@`($"H`#DB`2,`O`$ZZ!':PA4_O``QF7B!*T?P````,,!`(5
  1025. XM@``.,(`,A/____]F$B2J``@E:@`(``1P`!`#8`#^^D'Z_H8I2(=@($K1_```<
  1026. XM``PP$`C```XP@"2J``@@:@`0T=(E2``$(%)2DA"#<``0`V``_L8@2M'\````=
  1027. XM##`0",```C"`)6H`"``$)*H`"'#_8`#^IDY5__9(YS@@)&T`"'0`(`IG!DIJA
  1028. XM``QF"G#_3-\$'$Y=3G4(*@`!``QF"B\*3KK]J(2`6$\0*@`.2(!(P"\`3KH&Y
  1029. XMB(2`""H````-6$]G"B\J``A.N@&66$]*:@`49TY(>@!J2&W_]TZZ`E`X*@`4N
  1030. XM=@!03W``,`1R"DZZ`'P&@````#!R!Y*#0>W_]Q&`&`!(Q(G\``I2@PR#````)
  1031. XM!6W40BW__TAM__=.N@,26$]"DD*J``1"J@`(0FH`#$J"9P9P_V``_UAP`&``!
  1032. XM_U)435``2.=(`$*$2H!J!$2`4D1*@6H&1($*1``!83Y*1&<"1(!,WP`22H!./
  1033. XM=4CG2`!"A$J`:@1$@%)$2H%J`D2!81H@`6#8+P%A$B`!(A]*@$YU+P%A!B(?^
  1034. XM2H!.=4CG,`!(04I!9B!(038!-`!"0$A`@,,B`$A`,@*"PS`!0D%(04S?``Q.L
  1035. XM=4A!)@$B`$)!2$%(0$)`=`_0@-.!MH%B!)*#4D!1RO_R3-\`#$YU2.<@("1O0
  1036. XM``QT01`J``Y(@$C`+P!.N@$Z2H!83V<"="$E?```!```$$AX!`!.N@#&)4``F
  1037. XM"%A/9A@E?`````$`$"!*T?P````/)4@`"#0\`(`@2M'\````#'``,!`R`DC!Z
  1038. XM@($P@"5J``@`!"2J``A,WP0$3G5(YP`PE\LD;(=D8!`@2E"((F\`#+/(9PXFY
  1039. XM2B12(`IF[$S?#`!.=2`+9P0FDF`$*5*'9$CG``(@*@`$4(`B2BQLAS1.KO\N%
  1040. XM3-]``*.<`,"1LAV1@'"922.<``B`J``10@")*+&R'-$ZN_RY,WT``)$L@>
  1041. XM"F;@0JR'9$S?#`!.=4CG("`D+P`,2H)F"'``3-\$!$YU2.<``G(`(`)0@"QL^
  1042. XMAS1.KO\Z3-]``"1`2H!F!'``8-I!^O^6*4B':"2LAV0E0@`$*4J'9"`*4(!@K
  1043. XMP$SO`P``!"`($-EF_$YU2.<@("0O``QR!B`"3KH$3"1`U>R'/$J";0PP;(.(,
  1044. XML<)O!$J29A`I?`````.'+'#_3-\$!$YU2.<``G(&(`).N@0:(&R'/"(P"``L^
  1045. XM;(<X3J[_*$S?0`!*@&<$<`%@`G``8,Y(YS`@)"\`$$ZZ`6IR!B`"3KH#YB1`C
  1046. XMU>R'/$J";0PP;(.(L<)O!$J29A`I?`````.'+'#_3-\$#$YU2.<P`B`O`"137
  1047. XM@"8`)"\`("(2+&R'.$ZN_[Y,WT`,)@`,@/____]F&$CG``(L;(<X3J[_?$S?J
  1048. XM0``I0(<L</]@NDCG,`)V`'0`(A(L;(<X3J[_ODS?0`Q@HDCG``(B+P`(+&R'6
  1049. XM.$ZN_[A,WT``2H!F&$CG``(L;(<X3J[_?$S?0``I0(<L</].=7``8/I(YS`@?
  1050. XM)"\`$$ZZ`*1R!B`"3KH#("1`U>R'/$J";0PP;(.(L<)O!$J29A`I?`````.'/
  1051. XM+'#_3-\$#$YU,"H`!`)```-F#"E\````!H<L</]@Y`@J``,`!&<62.<P`G8!-
  1052. XM=``B$BQLASA.KO^^3-]`#$CG,`(F+P`D)"\`("(2+&R'.$ZN_]!,WT`,)@`,[
  1053. XM@/____]F&$CG``(L;(<X3J[_?$S?0``I0(<L</]@BB`#8(9(YR``2.<``B(\`
  1054. XM```0`'``+&R'-$ZN_LY,WT``)``(```,9Q)*K(=$9@@@`DS?``1.=4ZZ``9PX
  1055. XM`&#R2.<P`G8$0?H`+B0(+P,O`BQLASA.KO_$(@`D'R8?+&R'.$ZN_]!,WT`,^
  1056. XM2'@``4ZZ``I83TYU7D,*`$JLAVQG%"!LAVP@:``$3I`@;(=L*5"';&#F2JR'C
  1057. XM8&<&(&R'8$Z0+R\`!$ZZ``983TYU2.<P`"8O``Q*K(<\9S)T`&`*+P).N@%P2
  1058. XM6$]2@C!L@XBQPF[N2.<``C`L@XC!_``&(FR'/"QLAS1.KO\N3-]``$JLAVAG0
  1059. XM!B!LAVA.D$JL@XYG%$CG``(B+(..+&R'.$ZN_Z9,WT``2JR'<&<((&R'<""L_
  1060. XMAW1*K(=X9Q1(YP`"(FR'>"QLAS1.KOYB3-]``$JLAWQG%$CG``(B;(=\+&R'8
  1061. XM-$ZN_F),WT``2JR'@&<42.<``B)LAX`L;(<T3J[^8DS?0`!*K(>$9Q1(YP`"`
  1062. XM(FR'A"QLAS1.KOYB3-]``$CG``8L>``$""X`!`$I9Q!+^@`(3J[_XF`&0J?S7
  1063. XM7TYS*E]*K(=(9CQ*K(=89S1(YP`"("R'5")LAU@L;(<T3J[_+DS?0`!(YP`"=
  1064. XM("R'4.6`6(`B;(=,+&R'-$ZN_RY,WT``8"1(YP`"+&R'-$ZN_WQ,WT``2.<`!
  1065. XM`B)LAT@L;(<T3J[^ADS?0`!(YP`"(FR'."QLAS1.KOYB3-]``"`#+FR',$YUL
  1066. XM3-\`#$YU2.<@("0O``QR!B`"3KH`2B1`U>R'/$J";0PP;(.(L<)O!$J29A`II
  1067. XM?`````.'+'#_3-\$!$YU,"H`!`)`@`!F$DCG``(B$BQLASA.KO_<3-]``$*2!
  1068. XM<`!@V$CG<``T`<3`)@%(0\;`2$-"0]2#2$#`P4A`0D#0@DS?``Y.=0```^P`O
  1069. XM```!`````0``$-8````````#\@```^H```#D_____P`````````````'BP``\
  1070. XM!XX```>.```'BP``!Y$```>4```'E```!Y$```>7```'F@``!YH```>7```'G
  1071. XMG0``!Z````>@```'G0``!Z,```>F```'I@``!Z,```>I```'30``!TT```>I%
  1072. XM```'K```!Z\```>O```'K```#M0```[5```.[P``#P$```\5```/)P``#S,``
  1073. XM``]$```/6```#VP```]Z```/C```#Y8```^N```/OP``#]8```_H```/_@``R
  1074. XM$!(````3`"`@("`@("`@(#`P,#`P("`@("`@("`@("`@("`@("`@D$!`0$!`5
  1075. XM0$!`0$!`0$!`0`P,#`P,#`P,#`Q`0$!`0$!`"0D)"0D)`0$!`0$!`0$!`0$!Z
  1076. XM`0$!`0$!`0%`0$!`0$`*"@H*"@H"`@("`@("`@("`@("`@("`@("`D!`0$`@,
  1077. XM`````````````````````````````````````````````````````````````
  1078. XM`````````````````````````````````````````````````````````````
  1079. XM`````````````````````````````````````````````````````````````
  1080. XM`````````@````````$```````````````````0``0`````!````````````)
  1081. XM```````$``(``````0``````````````````````````````````````````'
  1082. XM`````````````````````````````````````````````````````````````
  1083. XM`````````````````````````````````````````````````````````````
  1084. XM`````````````````````````````````````````````````````````````
  1085. XM`````````````````````````````````````````````````````````````
  1086. XM`````````````````````````````````````````````````````````````
  1087. XM`````````````````````````````````````````````````````````````
  1088. XM`````````````````````````````````````````````````````````````
  1089. XM````````````````````````````````````````%``````````````#[```#
  1090. XM`"\`````````#````!`````4````&````!P````@````)````"@````L````K
  1091. XM,````#0````X````/````$````!$````2````$P```!0````5````%@```!<(
  1092. XM````8````&0```!H````;````'````!T````>````'P```"`````A````(@`\
  1093. XM``",````D````)0```"8````G````*````"D````J````*P```"P````M```@
  1094. XB`+@```"\````P````,0````````#\@```^L````!```#\JP`]
  1095. X``
  1096. Xend
  1097. Xsize 11104
  1098. END_OF_FILE
  1099. if test 15581 -ne `wc -c <'app.uu'`; then
  1100.     echo shar: \"'app.uu'\" unpacked with wrong size!
  1101. fi
  1102. # end of 'app.uu'
  1103. fi
  1104. if test -f 'makefile' -a "${1}" != "-c" ; then 
  1105.   echo shar: Will not clobber existing file \"'makefile'\"
  1106. else
  1107. echo shar: Extracting \"'makefile'\" \(271 characters\)
  1108. sed "s/^X//" >'makefile' <<'END_OF_FILE'
  1109. X# makefile for APP assembly preprocessor
  1110. X
  1111. XCFLAGS= -pa -so
  1112. X
  1113. Xapp:    app.o
  1114. X    ln app.o -lc
  1115. X
  1116. Xclean:
  1117. X    -delete #?.bak quiet
  1118. X    -delete #?.o quiet
  1119. X    -delete app
  1120. X    -delete app.UU
  1121. X    -delete app.shar
  1122. X
  1123. Xshar:    app
  1124. X    uuencode >app.UU app app
  1125. X    shar >app.shar README makefile app.c app.pro app.UU
  1126. END_OF_FILE
  1127. if test 271 -ne `wc -c <'makefile'`; then
  1128.     echo shar: \"'makefile'\" unpacked with wrong size!
  1129. fi
  1130. # end of 'makefile'
  1131. fi
  1132. echo shar: End of archive 1 \(of 1\).
  1133. cp /dev/null ark1isdone
  1134. MISSING=""
  1135. for I in 1 ; do
  1136.     if test ! -f ark${I}isdone ; then
  1137.     MISSING="${MISSING} ${I}"
  1138.     fi
  1139. done
  1140. if test "${MISSING}" = "" ; then
  1141.     echo You have the archive.
  1142.     rm -f ark[1-9]isdone
  1143. else
  1144.     echo You still need to unpack the following archives:
  1145.     echo "        " ${MISSING}
  1146. fi
  1147. ##  End of shell archive.
  1148. exit 0
  1149. -- 
  1150. Mail submissions (sources or binaries) to <amiga@cs.odu.edu>.
  1151. Mail comments to the moderator at <amiga-request@cs.odu.edu>.
  1152. Post requests for sources, and general discussion to comp.sys.amiga.
  1153.